require('dotenv').config();
const express = require('express');
const cors = require('cors');
const helmet = require('helmet');
const morgan = require('morgan');
const rateLimit = require('express-rate-limit');

const connectDB = require('./config/database');
const logger = require('./utils/logger');
const { errorResponse, internalErrorResponse } = require('./utils/response');

// 创建Express应用
const app = express();

// 连接数据库
connectDB();

// 安全中间件
app.use(helmet({
  contentSecurityPolicy: {
    directives: {
      defaultSrc: ["'self'"],
      styleSrc: ["'self'", "'unsafe-inline'"],
      scriptSrc: ["'self'"],
      imgSrc: ["'self'", "data:", "https:"],
    },
  },
}));

// CORS配置
const corsOptions = {
  origin: function (origin, callback) {
    const allowedOrigins = [
      'http://localhost:8080', // Docker前端服务
      'http://localhost:5173', // Vite开发服务器
      'http://localhost:3000', // 备用前端端口
      'http://127.0.0.1:8080',
      'http://127.0.0.1:5173',
      'http://127.0.0.1:3000',
      'http://172.18.0.4', // Docker内部前端容器
      'http://172.18.0.4:80' // Docker内部前端容器带端口
    ];
    
    // 允许无origin的请求（如移动应用、Postman等）
    if (!origin) return callback(null, true);
    
    if (allowedOrigins.indexOf(origin) !== -1) {
      callback(null, true);
    } else {
      callback(new Error('CORS策略不允许此来源'));
    }
  },
  credentials: true,
  optionsSuccessStatus: 200
};

app.use(cors(corsOptions));

// 限流中间件
const limiter = rateLimit({
  windowMs: parseInt(process.env.RATE_LIMIT_WINDOW_MS) || 15 * 60 * 1000, // 15分钟
  max: parseInt(process.env.RATE_LIMIT_MAX) || 100, // 限制每个IP 100个请求
  message: {
    success: false,
    code: 429,
    message: '请求过于频繁，请稍后再试',
    timestamp: new Date().toISOString()
  },
  standardHeaders: true,
  legacyHeaders: false,
});

app.use('/api', limiter);

// 日志中间件
if (process.env.NODE_ENV !== 'test') {
  app.use(morgan('combined', {
    stream: {
      write: (message) => logger.info(message.trim())
    }
  }));
}

// 解析中间件
app.use(express.json({ limit: '10mb' }));
app.use(express.urlencoded({ extended: true, limit: '10mb' }));

// 静态文件服务
app.use('/uploads', express.static('uploads'));

// 健康检查
app.get('/api/v1/health', (req, res) => {
  res.json({
    success: true,
    code: 200,
    message: '服务运行正常',
    data: {
      status: 'healthy',
      timestamp: new Date().toISOString(),
      uptime: process.uptime(),
      environment: process.env.NODE_ENV,
      version: '1.0.0'
    }
  });
});

// API路由
const apiRoutes = require('./routes/index');
app.use('/api/v1', apiRoutes);

// 404处理
app.use((req, res) => {
  res.status(404).json({
    success: false,
    code: 404,
    message: `API路径 ${req.originalUrl} 不存在`,
    timestamp: new Date().toISOString()
  });
});

// 全局错误处理中间件
app.use((error, req, res, next) => {
  logger.error('全局错误处理:', {
    error: error.message,
    stack: error.stack,
    url: req.originalUrl,
    method: req.method,
    ip: req.ip,
    userAgent: req.get('User-Agent')
  });

  // 处理特定错误类型
  if (error.name === 'ValidationError') {
    return res.status(400).json({
      success: false,
      code: 400,
      message: '数据验证失败',
      error: error.message,
      timestamp: new Date().toISOString()
    });
  }

  if (error.name === 'CastError') {
    return res.status(400).json({
      success: false,
      code: 400,
      message: '无效的数据格式',
      timestamp: new Date().toISOString()
    });
  }

  if (error.code === 11000) {
    return res.status(409).json({
      success: false,
      code: 409,
      message: '数据已存在',
      timestamp: new Date().toISOString()
    });
  }

  // 默认错误响应
  return internalErrorResponse(res, error);
});


module.exports = app;